#![allow(dead_code)]
use crate::domain::CountNum;
use crate::domain::OrderItemBean;
use crate::domain::OrderItemQueryRequest;
use crate::domain::GoodsBean;
use crate::serviceimpl::init_db;
use crate::utils::string_util::is_digit;
use crate::utils::string_util::right_find_under_line;
use crate::serviceimpl::goods_service::find_goods_by_id as service_find_goods_by_id;
use sqlx::Error;
use substring::Substring;

pub async fn activate_all_order_items(ids:Vec<i64>) ->Result<u64, Error> {
	let app_state = init_db();
	let order_items = &app_state.await.context.order_items;
	let vecter_iterator = ids.iter();
	for order_item_id in vecter_iterator {
		let _ = order_items.activate_order_item(*order_item_id).await;
	}
	Ok(0)
}

pub async fn activate_order_item(id:i64) ->Result<u64, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.activate_order_item(id).await
}

pub async fn add_order_item(order_item:OrderItemBean) ->Result<u64, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.add_order_item(order_item).await
}

pub async fn clone_all_order_items(ids:Vec<i64>) ->Result<u64, Error> {
	let vecter_iterator = ids.iter();
	for order_item_id in vecter_iterator {
		let _ = clone_order_item(*order_item_id).await;
	}
	Ok(0)
}

pub async fn clone_order_item(id:i64) ->Result<u64, Error> {
	let mut order_item = find_order_item_by_id(id).await.unwrap();
	let name = find_order_item_indexed_name(order_item.name).await.unwrap();
	order_item.name = name;
	add_order_item(order_item).await
}

pub async fn count_search_order_items_by_fields_records(order_item_query_request:OrderItemQueryRequest) ->Result<CountNum, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.count_search_order_items_by_fields_records(order_item_query_request).await
}

pub async fn delete_all_order_items(ids:Vec<i64>) ->Result<u64, Error> {
	let app_state = init_db();
	let order_items = &app_state.await.context.order_items;
	let vecter_iterator = ids.iter();
	for order_item_id in vecter_iterator {
		let _ = order_items.delete_order_item(*order_item_id).await;
	}
	Ok(0)
}

pub async fn delete_order_item(id:i64) ->Result<u64, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.delete_order_item(id).await
}

pub async fn find_order_item_by_id(id:i64) ->Result<OrderItemBean, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.find_order_item_by_id(id).await
}

pub async fn find_order_item_by_name(name:String) ->Result<OrderItemBean, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.find_order_item_by_name(name).await
}

pub async fn list_active_order_items() ->Result<Vec<OrderItemBean>, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.list_active_order_items().await
}

pub async fn list_all_order_items() ->Result<Vec<OrderItemBean>, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.list_all_order_items().await
}

pub async fn search_order_items_by_fields(order_item_query_request:OrderItemQueryRequest) ->Result<Vec<OrderItemBean>, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.search_order_items_by_fields(order_item_query_request).await
}

pub async fn search_order_items_by_fields_by_page(order_item_query_request:OrderItemQueryRequest) ->Result<Vec<OrderItemBean>, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.search_order_items_by_fields_by_page(order_item_query_request).await
}

pub async fn soft_delete_all_order_items(ids:Vec<i64>) ->Result<u64, Error> {
	let app_state = init_db();
	let order_items = &app_state.await.context.order_items;
	let vecter_iterator = ids.iter();
	for order_item_id in vecter_iterator {
		let _ = order_items.soft_delete_order_item(*order_item_id).await;
	}
	Ok(0)
}

pub async fn soft_delete_order_item(id:i64) ->Result<u64, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.soft_delete_order_item(id).await
}

pub async fn toggle_one_order_item(id:i64) ->Result<u64, Error> {
	let app_state = init_db();
	let order_items = &app_state.await.context.order_items;
	let order_item = order_items.find_order_item_by_id(id).await.unwrap();
	if order_item.active == false {
		let _ = order_items.toggle_order_item(id).await;
	} else {
		let count = order_items.count_active_order_item_records().await.unwrap();
		if count.count_num > 1 {
			let _ = order_items.toggle_order_item(id).await;
		}
	}
	Ok(0)
}

pub async fn toggle_order_item(id:i64) ->Result<u64, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.toggle_order_item(id).await
}

pub async fn update_order_item(order_item:OrderItemBean) ->Result<u64, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.update_order_item(order_item).await
}

pub async fn find_order_item_indexed_name(name:String) ->Result<String, Error> {
	let mut short_name = name.clone();
	if name.contains("_") && is_digit(name.substring(right_find_under_line(name.clone())+1,name.chars().count()).to_string()) {
		short_name = name.substring(0,right_find_under_line(name.clone())).to_string();
	}

	let app_state = init_db();
	let order_items = app_state.await.context.order_items.find_order_item_indexed_name(short_name.clone()).await.unwrap();

	let mut index_num = 1;
	for order_item in order_items {
		let name2 = order_item.name;
		if name2.contains("_") && is_digit(name2.substring(right_find_under_line(name2.clone())+1,name2.chars().count()).to_string()) {
			let index = name2.substring(right_find_under_line(name2.clone())+1,name2.chars().count()).parse::<i32>().unwrap();
			if index >= index_num {
				index_num = index + 1;
			}
		}
	}

	let index_name = short_name.clone() + "_" + &index_num.to_string();
	Ok(index_name)
}

pub async fn validate_order_items(order_items:Vec<OrderItemBean>) -> Result<bool, Error> {
    for order_item in order_items {
        let goods:GoodsBean = service_find_goods_by_id(order_item.goods_id).await.unwrap();
        if goods.stock < order_item.amount {
            return Ok(false);
        }
    }
    Ok(true)
}

pub async fn list_my_order_items(cust_order_id:i64) ->Result<Vec<OrderItemBean>, Error> {
	let app_state = init_db();
	app_state.await.context.order_items.list_my_order_items(cust_order_id).await
}
